<template>
  <div class="panel">
    <div class="close-header">
      <div class="user-name">
        用户名称：<span>{{ currentChat.nikeName }}</span>
      </div>
      <div class="close-icon" @click="onClose">
        <i class="el-icon-close"></i>
      </div>
    </div>
    <div class="chat-show-cover" ref="cover" id="cover">
      <div v-if="currentChat.meetingId">
        <div class="load-more" v-if="moreLoading && !noMore">
          <i class="el-icon-loading"></i>
        </div>
        <!-- <div class="load-more" v-if="noMore && messages.length > 0">
          <span>没有更多了</span>
        </div> -->
      </div>
      <div
        class="chat-show-wrap"
        ref="wrap"
        v-if="messages.length && currentChat.meetingId"
      >
        <message-component
          v-for="(message, i) in messages"
          :key="i"
          :message="message"
          :ref="'msg' + message.id"
        ></message-component>
      </div>
    </div>
    <div class="chat-tool-cover">
      <el-upload
        class="upload-demo"
        action=""
        :accept="imgUploadType"
        :before-upload="beforeUpload"
        :show-file-list="false"
        :http-request="() => {}"
      >
        <i class="el-icon-picture-outline"></i>
      </el-upload>
      <!-- <i class="el-icon-camera"></i>
      <i class="el-icon-upload2"></i> -->
    </div>
    <div class="chat-input-cover clearfix">
      <textarea
        ref="textVal"
        class="input-textarea"
        v-model.trim="txt"
        @focus="onfocus"
        @blur="onblur"
        @keydown="onKeydown"
        @keyup="onKeyup"
      ></textarea>
      <el-button class="send-btn" type="primary" @click="inputHandler('text')"
        >发送</el-button
      >
    </div>
    <el-dialog
      title="图片预览"
      :visible.sync="dialogImgVisible"
      class="coustom-width"
    >
      <div v-loading="imgUpLoading">
        <img width="100%" :src="imgUrl" alt="" />
        <div class="dialog-footer">
          <el-button @click="dialogImgVisible = false">取 消</el-button>
          <el-button type="primary" @click="handlerUpload">确 定</el-button>
        </div>
      </div>
    </el-dialog>
  </div>
</template>

<script>
import messageComponent from "./message-component";
import { MessageModel } from "../model/message";
import { mapMutations, mapState } from "vuex";
import { uploadFile, queryMeetingDetail } from "@/api/chat";
import { msgBody,transTimestamp } from "../utils";
export default {
  name: "chat-panel",
  components: {
    messageComponent,
  },
  data() {
    return {
      txt: "",
      messages: [],
      fileList: [],
      moreLoading: false,
      pageNum: 1,
      pageSize: 10,
      coverDOM: {},
      stopScorllTop: null,
      focus: false,
      imgUploadType: ".jpg,.jpeg,.png",
      sendState: true,
      InputTimer: null,
      stopInputTime: 60000, //光标停止一分钟，更改正在输入状态
      dialogImgVisible: false,
      fileObj: {},
      imgUrl: "",
      imgUpLoading: false,
      noMore: false,
      pressShift: false,
    };
  },
  props: {
    recieve: {
      type: Object,
    },
  },
  computed: {
    ...mapState([
      "currentChat",
      "idStore",
      "chatRecords",
      "shortcutContent",
      "currentCloseMeetingId",
    ]),
  },
  watch: {
    recieve: {
      handler(newVal) {
        const message = new MessageModel(newVal);
        const id = message.id;
        this.messages.push(message);
        this.$nextTick(function () {
          //滚动条滑动到底部
          const ele = "msg" + id;
          this.$refs[ele][0] && this.$refs[ele][0].$el.scrollIntoView();
        });
      },
      deep: true,
    },
    "currentChat.meetingId": {
      async handler() {
        this.pageSize = 10;
        this.noMore = false;
        await this.getHistory();
        this.$nextTick( ()=> {
          //滚动条滑动到底部
          if (this.messages.length) {
            const id = this.messages[this.messages.length - 1].id;
            const ele = "msg" + id;
            this.$refs[ele][0].$el.scrollIntoView();
          }
           this.$refs.textVal.focus()
        });
      },
    },
    txt(newVal) {
      this.InputTimer && clearTimeout(this.InputTimer);
      this.InputTimer = setTimeout(() => {
        this.onblur();
      }, this.stopInputTime);
      if (newVal && this.focus && this.sendState) {
        const data = { type: "incoming", content: "" };
        this.$emit("send", data);
        this.sendState = false;
      }
    },
    shortcutContent: {
      handler(newVal) {
        console.log('shortcutContent',newVal)
        const { type, txt } = newVal;
        this.txt = txt;
        if (type == 1) {
          //知识库直接发送
          this.inputHandler("text");
        }
        if (type == 2) {
          //工具发送
          this.inputHandler("link");
        }
      },
      deep: true,
    },
    currentCloseMeetingId() {
      this.messages = [];
    },
  },
  mounted() {
    this.coverDOM = this.$refs.cover;
    this.coverDOM.onscroll = async () => {
      if (this.coverDOM.scrollTop === 0 && !this.noMore) {
        const id = this.messages[0].id;
        await this.getHistory(this.currentChat.meetingId);
        this.$nextTick(function () {
          const ele = "msg" + id;
          this.$refs[ele][0].$el.scrollIntoView();
        });
      }
    };
  },
  methods: {
    ...mapMutations(["updateChatRecords", "setCloseCurrent"]),
    inputHandler(type) {
      if (!this.txt) {
        return;
      }
      let txt = "";
      if (type === "text") {
        txt = this.txt.replace(/[\r\n]/g, "<br/>").replace(/\s/g, "&nbsp;");
      } else {
        txt = this.txt;
      }
      this.pushOut(txt, type);
      this.txt = "";
    },
    // 发送消息通知父组件
    pushOut(info, type) {
      //'text','img','voice'
      if (!this.currentChat.meetingId) {
        this.$message.warning("请选择用户");
        return;
      }
      // const msg = { from: 0, type: type === "text" ? 0 : 1, content: info };
      // const message = new MessageModel(msg);
      // this.messages.push(message);
      const data = { content: info, type };
      this.$emit("send", data);
    },
    onfocus() {
      if (this.currentChat.meetingId) {
        this.focus = true;
      }
    },
    onblur() {
      this.InputTimer && clearTimeout(this.InputTimer);
      this.sendState = true;
      if (this.currentChat.meetingId) {
        const data = { type: "comecompelet", content: "" };
        this.focus = false;
        this.$emit("send", data);
      }
    },
    onKeydown(e) {
      if (e.keyCode === 16) {
        this.pressShift = true;
      } else if (e.keyCode === 13) {
        !this.pressShift && this.inputHandler("text");
      } else {
        this.pressShift = false;
      }
    },
    onKeyup() {
      this.pressShift = false;
    },
    onClose() {
      if (!this.currentChat.memberId) {
        this.$message.warning("请选择用户");
        return;
      }
      this.setCloseCurrent(true);
    },
    lookMore() {
      this.getHistory();
    },
    async getHistory() {
      if (this.moreLoading) {
        return;
      }
      const params = {
        meetingId: this.currentChat.meetingId,
        pageNum: this.pageNum,
        pageSize: this.pageSize,
      };
      this.moreLoading = true;
      await queryMeetingDetail(params)
        .then((res) => {
          const {
            data: { list, total },
          } = res;
          if (this.pageSize > total) {
            this.noMore = true;
          } else {
            this.pageSize += 10;
          }
          this.messages = [];
          list.forEach((item) => {
            let msg = {
              id: item.id,
              time: item.serverTime,
              content: item.content,
            };
            let params = {};
            if (item.contentType == "0x58") {
              const { isTrue, opinionRating, feedback } = JSON.parse(
                item.content
              );
              //连接
              msg = {
                id: item.id,
                time: item.serverTime,
                comment: `客户评价:【问题${
                  Number(isTrue) == 1 ? "已" : "未"
                }解决】,【${Number(opinionRating)}颗星】${
                  feedback ? `,【${feedback}】` : ""
                }`,
              };
              params = {
                from: item.talkerType == "1" ? 0 : 1,
                type: 4,
              };
            }
            if (item.contentType == "0x41" || item.contentType == "79") {
              //文字
              params = {
                from: item.talkerType == "1" ? 0 : 1,
                type: 0, //文字|图片|语音
              };
            }
            if (item.contentType == "0x45") {
              //图片
              params = {
                from: item.talkerType == "1" ? 0 : 1,
                type: 1,
              };
            }
            if (item.contentType == "0x62") {
              //连接
              msg = {
                id: item.id,
                time: item.serverTime,
                content: JSON.parse(item.content).toolName,
              };
              params = {
                from: item.talkerType == "1" ? 0 : 1,
                type: 3,
              };
            }
            if (item.contentType == "0x76" || item.contentType == "0x77") {
              //验证消息
              params = {
                from: item.talkerType == "1" ? 0 : 1,
                type: 5,
              };
            }
            const message = new MessageModel({ ...params, ...msg });
            this.messages.unshift(message);
            if (item.contentType == "0x79") {//自己发的欢迎辞
              //穿插时间
              msg = {
                id: item.id,
                time: item.serverTime,
                content: transTimestamp(item.serverTime),
                from: item.talkerType == "1" ? 0 : 1,
                type: 5,
              };
              this.messages.unshift(new MessageModel(msg));
            }
          });
        })
        .catch(() => {
          this.noMore = false;
          this.$message.error(`查询历史记录异常`);
        })
        .finally(() => {
          this.moreLoading = false;
        });
    },
    beforeUpload(file) {
      this.fileObj = file;
      const { name } = file;
      const index = name.lastIndexOf(".");
      const fileType = name.slice(index);
      if (this.imgUploadType.indexOf(fileType) < 0) {
        this.$message.warning(
          `上传图片格式有误，支持格式${this.imgUploadType}`
        );
        return false;
      }
      let reader = new FileReader();
      reader.readAsDataURL(this.fileObj);
      reader.onload = (e) => {
        this.imgUrl = e.target.result;
        this.dialogImgVisible = true;
      };
      return true;
    },
    handlerUpload() {
      this.imgUpLoading = true;
      const form = new FormData();
      form.append("file", this.fileObj);
      const params = {
        meetingId: "",
        memberId: "",
        waiterId: "",
        contentType: "",
      };
      const fomatMsg = msgBody(params);
      form.append("body", JSON.stringify(fomatMsg));
      uploadFile(form)
        .then((res) => {
          this.dialogImgVisible = false;
          const { data } = res;
          this.txt = data[0].url;
          this.inputHandler("img");
        })
        .catch(() => {
          this.$message.error(`上传图片异常`);
        })
        .finally(() => {
          this.imgUpLoading = false;
        });
    },
  },
};
</script>
<style lang="scss" scoped>
.panel {
  display: flex;
  flex-direction: column;
  height: 100%;
}
.close-header {
  height: 40px;
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 0 20px;
  border-top: 1px solid #f2f2f2;
  border-bottom: 1px solid #f2f2f2;
  .user-name {
    span {
      display: inline-block;
      padding-left: 4px;
      color: #666;
    }
  }
}
.close-icon {
  cursor: pointer;
}
.chat-show-cover {
  padding: 0;
  flex: 1;
  overflow-y: auto;
  // border-radius: 10px;
}
.load-more {
  text-align: center;
  font-size: 16px;
  padding-top: 12px;
  span {
    font-size: 12px;
    color: #999;
    cursor: pointer;
  }
}
.chat-tool-cover {
  border-top: 1px solid #f2f2f2;
  height: 30px;
  display: flex;
  justify-content: flex-start;
  align-items: center;
  i {
    font-size: 22px;
    margin: 0 12px;
  }
}
.chat-input-cover {
  .send-btn {
    float: right;
    margin-right: 10px;
    margin-bottom: 10px;
  }
  border-bottom: 1px solid #f2f2f2;
}
.input-textarea {
  width: 100%;
  height: 140px;
  padding: 10px 30px;
  border: none;
  // border-radius: 10px;
  resize: none;
  font-size: 16px;
  outline: none;
}
.dialog-footer {
  margin-top: 8px;
  display: flex;
  justify-content: flex-end;
}
.coustom-width {
  ::v-deep .el-dialog {
    width: 600px;
  }
}
</style>